"""
This is used to analysis the relation between real time and simulation years
how many seconds need to run a 15 year's game 
"""
import os,sys,string, DB
from Configuration import Configuration
from scipy import *
from numpy import array
from scipy import stats,signal, optimize
import numpy, matplotlib
from numpy.random import randn
import scipy.spatial

def barplot(x, y):
    width = 0.35
    n = numpy.arange(len(x))
    p1 = matplotlib.pyplot.bar(n, y,  width, color='r')
    matplotlib.pyplot.xticks(n, x)
    matplotlib.pyplot.show()

def barplot_witherror(x, y, e):
    width = 0.35
    n = numpy.arange(len(x))
    fig = matplotlib.pyplot.figure()
    ax = fig.add_subplot(111)
    p1 = ax.bar(n, y,  width, yerr = e, color='r')
    matplotlib.pyplot.xticks(n, x)
    for label in ax.xaxis.get_ticklabels():
        label.set_color('red')
        label.set_rotation(45)
        label.set_fontsize(5)



def barplotTwo(x, y1, y2):
    width = 0.35
    n = numpy.arange(len(x))
    p1 = matplotlib.pyplot.bar(n, y1, color='r')
    p2 = matplotlib.pyplot.bar(n+width, y2, color='y')
    matplotlib.pyplot.xticks(n + width, x)
    matplotlib.pyplot.show()


def analysis(expName, maxTurn, maxVar):
    dir = os.path.join("..", "test_result", expName, "analysis")
    for i in xrange(1, maxTurn + 1):
        for j in xrange(1, maxVar+1):
            filename = os.path.join(dir, "%d"%i+"_%d"%j + ".txt")
            file = open(filename)
            lines = file.readlines()
            line = lines[0]
            startTime = string.atof(line.split()[0])
            endTime = string.atof(line.split()[1])
            line = lines[len(lines) -1]
            words = string.split(line)
            print "%d"%i+"_%d"%j, endTime - startTime, startTime, endTime, "cpu time", words[3]


def showTime(expId, expName, low, upper, isShow = True):
    maxId = Configuration.getId()
    timeArray = {0:0}
    countArray = {0:0}
    for i in xrange(1, upper + 1):
        countArray[i] = 0
        timeArray[i] = 0
    for id in xrange(1, maxId+1/1):
        if(expId != 0 and id !=expId):
            continue
        lines = DB.getAllTime(id, expName)
        for line in lines:
            if(line[2] <= 0): continue
            print line
            timeArray[line[1]] = timeArray[line[1]] + line[2]
            countArray[line[1]] = countArray[line[1]] + 1
    x = []
    y = []
    for i in xrange(low, upper + 1):
#        print i, timeArray[i]/countArray[i]
        x.append(i)
        y.append(timeArray[i]/countArray[i])
    if(isShow):
        barplot(x, y)

    return (x,y)

def mean(x):
    return scipy.mean(x)

def linearRegression(x, y, filename, extend = 5, isShow = False):
    import matplotlib.pyplot
    matplotlib.pyplot.clf()
    (a_s,b_s,r_value,p_value,stderr)= stats.linregress(x,y)
    print "a = %f, b = %f, stderr = %f, r_value = %f, p_value = %f"%(a_s,b_s,stderr, r_value, p_value)
    nx = xrange(1, len(x)+extend)
    ny = polyval([a_s,b_s], nx)
    matplotlib.pyplot.plot(x,y, 'go--')
    matplotlib.pyplot.plot(nx,ny, 'kx')
    matplotlib.pyplot.legend(['original','regression'], ncol=3, loc = 2)
    filename = os.path.join("..","png", filename)
    matplotlib.pyplot.savefig(filename)
    print "linegression " + filename
    if isShow == True:
        matplotlib.pyplot.show()
"""
Read time from data based and predictTimeSeries it 
"""
def predictTimeLinearRegression(expId, expName, low, upper, isShow = True):
    ret = showTime(expId, expName, low, upper, False)
    x = ret[0]
    y = ret[1]
    filename = "%d_"%expId + expName + "_(%d to %d)_cputime_prediction.png"%(low,upper)
    path = os.path.join("..", "test_result", expName, "analysis", filename)
    linearRegression(x,y,path, 5, isShow)
    #if the p-value is less than 0.05 or 0.01, corresponding respectively to a 5% or 1% chance of rejecting the null hypothesis when it is true (Type I error).

def multiVariableRegression():
    import ols
    data = randn(100,5)
#    print len(data)
#    print data
    y = data[:,0]
    x = data[:,1:]
    mymodel = ols.ols(y,x,'y',['x1','x2','x3','x4'])
    print mymodel.p               # return coefficient p-values
    mymodel.summary()

def correlationOfTwoVector(x, y):
    if len(x) < len(y):
        x1 = array(x)
        x2 = array(y)
    else:
        x1 = array(y)
        x2 = array(x)
#    print "len ", len(x1),len(x2)
    l = len(x2) - len(x1)
    i = 0 
    ret = scipy.spatial.distance.braycurtis(x1, x2[i:len(x1)+i])
#    return (min(ret), max(ret))
    return ret

def correlation(aId, bId, expName, factor):
    path1 = os.path.join("..", "test_result", "trunk")
    fn1 = os.path.join(path1, "%d_"%aId + expName + "_1_%d"%factor+"_cpu.txt" )
    fn2 = os.path.join(path1, "%d_"%bId + expName + "_1_%d"%factor+"_cpu.txt")
#    x = scipy.linspace(-10, 10, num=100)

    print fn1, fn2
    x1 = getCPU(fn1)
    x2 = getCPU(fn2)
    print len(x1), len(x2)
    l = min(len(x1), len(x2))
    import scipy.spatial
    for i in xrange(0, len(x2)-l):
#        print len(x1), len(x2[i:l-1+i])
        print scipy.spatial.distance.correlation(x1, x2[i:l+i])
#    y = signal.correlate(x1,x2,mode='full')
#    t1 = linspace(1, len(x1) -1, len(x1))
#    t2 = linspace(1, len(x2) -1, len(x2))
#    ty = linspace(1, len(y) - 1, len(y))
#    print len(t1), len(y)
#    plot(t1,x1,'ro')
#    plot(t2,x2,'bo')
#    plot(ty,y, 'g-')
#    show()

def getCPU(filename):
    f = open(filename)
    x = []
    lines = f.readlines()
    for line in lines:
        x.append(string.atof(string.split(line)[1]))
    return array(x)

def predictTimeSeries(expName):
    dir = os.path.join("..", "test_result", expName)
    childDir = os.path.join(dir, "analysis")
    d = []
    for pth in xrange(1, 12/1):
        filename = "1_%d"%pth + ".txt_simplified"
        file = open(os.path.join(childDir,filename))
        lines = file.readlines()
        times = string.split(lines[0])
#            print times
#            print math.floor(string.atof(times[0])), math.floor(string.atof(times[1]))
        firsttime = pretime = string.atof(times[0])
        count = 1 
        total1 = total2 = 0
        for i in xrange(1, len(lines)/1):
            tuple = string.split(lines[i])
            input = []
            input.append(pth/100)
            input.append(string.atof(tuple[0])/10000)
            output = []
            output.append(string.atof(tuple[1])/100)
            d.append([input, output])
    print "total data set %d"%len(d)
    from bpnn import NN
    import pickle
    if os.path.exists("nn"):
        n = pickle.load(open("nn"))
#        n.train(d)
#        pickle.dump(n, open("nn", "w"))
    else:
        n = NN(2, 4, 1)
        # train it with some patterns
        n.train(d)
        pickle.dump(n, open("nn", "w"))
    
    # test it
    for i in xrange(1, 800/1):
        input = [0.01, i * 1.0/ 10000.0]
        print n.update(input)
        
def predictTimeANN(expId, expName, low, upper):
    x,y = showTime(expId, expName, low, upper, False)
    d = [] 
    print x,y
    for i in xrange(0, len(x)):
        d.append([[x[i]/10.0],[y[i]/228.0]])  
    print "total data set %d"%len(d)
    from bpnn import NN
    n = NN(1, 3, 1)
    # train it with some patterns
    n.train(d)
    x2 = xrange(1, len(x) + 1)
    y2 = []
    for i in xrange(0, len(x2)):
        y2.append(n.update([x2[i]/10.0]) * 228)
    matplotlib.pyplot.plot(x,y,'r')
    matplotlib.pyplot.plot(x2,y2,'g')
    matplotlib.pyplot.show()

def predictTimeFunctionFit(fun, expId, expName, low, upper, p0):
    x,y = showTime(expId, expName, low, upper, False)
    errfunc = lambda p, x1, y1: fun(p, x1) -y1
    p1, success = optimize.leastsq(errfunc, p0[:], args=(x,y))
    x2 = xrange(x[0], x[0] + len(x) + 2)
    print p1, " ", success
    nx1 = array(x)
    nx2 = array(x2)
    if( expName == "1a2"):
        nx1 = array(x) + 5
        nx2 = array(x2)+ 5
    matplotlib.pyplot.plot(nx1,y, 'ro')
    matplotlib.pyplot.plot(nx2, fun(p1,x2),'g')
    matplotlib.pyplot.legend(['original','regression'])
    matplotlib.pyplot.show()
    return True        

if __name__ == "__main__":
    correlation(1, 32, "1a1", 1)
#    analysis("1a1", 2, 8)
#    predictTimeLinearRegression("1a1", 1, 16)
#    multiVariableRegression()
#    x1 = [1,2,3,4,5]
#    x2 = [1,2,3,4,5]
#    y = signal.correlate(array(x1), array(x2))
#    t = scipy.linspace(-len(y)/2, len(y)/2, len(y))
#    plot(t,y)
#    show()
#    predictTimeLinearRegression(43, "1a1",1,16)
    fun = lambda p, x: p[0]**x + p[1]
    predictTimeFunctionFit(fun, 32, "1a2", 1, 6, [2, 20])
    p = []
    fun = lambda p, x: p[0]*x * numpy.sin(p[1] * x + p[2]) + p[3] * x
    predictTimeFunctionFit(fun, 43, "1a1", 1, 16, [0,1,1,1])
#    predictTimeLinearRegression(32, "1a3", 1, 4);
    showTime(32, "1a3", 1,4, True)
#    predictTimeANN(32, "1a2", 1, 6)
#    showTime(32 , "1a2", 1, 6,True)
#    predictTimeLinearRegression(32, "1a1",1,16)
    
    


